﻿using System;
using System.Collections.Generic;
using System.Collections.Specialized;
using System.Linq;
using System.Reflection;
using System.Web;
using System.Web.Mvc;
using Newtonsoft.Json;
using WSPay.Alipay;
using WSPay.Application;
using WSPay.Common;
using WSPay.Common.Log;
using WSPay.Core.DTO;
using WSPay.Domain;


namespace WSPay.Web.Controllers
{
    public class AliPayController : Controller
    {
        public IWSBService WSBService
        {
            get; private set;
        }

        public AliPayController(IWSBService wsbService)
        {
            WSBService = wsbService;
        }

        public ActionResult Test(ChargeDto dto)
        {
            return View(dto);
        }

        /// <summary>
        /// 用户充值
        /// </summary>
        /// <returns></returns>
        [HttpPost]
        public ActionResult Charge(ChargeDto dto)
        {
            //dto.ReturnUrl = "";
            //Type type = dto.GetType();
            //PropertyInfo[] t = type.GetProperties();
            //Dictionary<string,string> dic=new Dictionary<string, string>();
            //foreach (var item in t)
            //{
            //   dic.Add(item.Name,item.GetValue(dto).ToString()); 
            //}
            //return Json(dic,JsonRequestBehavior.AllowGet);
            try
            {
                var order = WSBService.CreateWSBRechargeBill(dto);
                var noticeUrl= Url.AbsoluteAction("Notify", "AliPay");
                //var noticeUrl= Url.AbsoluteAction("NotifyMobile", "AliPay");
                var amount = order.PayAmount;
                if (amount < 1)
                {
                   throw new ApplicationException("充值金额需大于1");
                }
                SortedDictionary<string, string> sParaTemp = new SortedDictionary<string, string>();
                sParaTemp.Add("service", Config.service);
                sParaTemp.Add("partner", Config.partner);
                sParaTemp.Add("seller_id", Config.seller_id);
                sParaTemp.Add("_input_charset", Config.input_charset.ToUpper());
                sParaTemp.Add("payment_type", Config.payment_type);
                sParaTemp.Add("notify_url", noticeUrl);
                sParaTemp.Add("return_url", dto.ReturnUrl);
                sParaTemp.Add("anti_phishing_key", Config.anti_phishing_key);
                sParaTemp.Add("exter_invoke_ip", Config.exter_invoke_ip);
                sParaTemp.Add("out_trade_no", order.OrderId);
                sParaTemp.Add("subject", dto.OrderInfo);
                sParaTemp.Add("total_fee", order.PayAmount.ToString("0.00"));//order.PayAmount.ToString("0.00")
                //sParaTemp.Add("total_fee", "0.01");//order.PayAmount.ToString("0.00")
                sParaTemp.Add("body", dto.OrderInfo);
                AlipaySubmit.BuildRequest(sParaTemp, "POST", "确认");
                return Content("");
            }
            catch (Exception e)
            {
                throw new ApplicationException(e.Message);
            }

        }
        /// <summary>
        /// wap站用户充值
        /// </summary>
        /// <returns></returns>
        [HttpPost]
        public ActionResult WapCharge(ChargeDto dto)
        {
            //dto.ReturnUrl = "";
            //Type type = dto.GetType();
            //PropertyInfo[] t = type.GetProperties();
            //Dictionary<string,string> dic=new Dictionary<string, string>();
            //foreach (var item in t)
            //{
            //   dic.Add(item.Name,item.GetValue(dto).ToString()); 
            //}
            //return Json(dic,JsonRequestBehavior.AllowGet);
            try
            {
                var order = WSBService.CreateWSBRechargeBill(dto);
                var noticeUrl = Url.AbsoluteAction("Notify", "AliPay");
                //var noticeUrl= Url.AbsoluteAction("NotifyMobile", "AliPay");
                var amount = order.PayAmount;
                if (amount < 1)
                {
                    throw new ApplicationException("充值金额需大于1");
                }
                SortedDictionary<string, string> sParaTemp = new SortedDictionary<string, string>();
                sParaTemp.Add("service", Config.mobileService);
                sParaTemp.Add("partner", Config.partner);
                sParaTemp.Add("seller_id", Config.seller_id);
                sParaTemp.Add("_input_charset", Config.input_charset.ToUpper());
                sParaTemp.Add("payment_type", Config.payment_type);
                sParaTemp.Add("notify_url", noticeUrl);
                sParaTemp.Add("return_url", dto.ReturnUrl);
                sParaTemp.Add("anti_phishing_key", Config.anti_phishing_key);
                sParaTemp.Add("exter_invoke_ip", Config.exter_invoke_ip);
                sParaTemp.Add("out_trade_no", order.OrderId);
                sParaTemp.Add("subject", dto.OrderInfo);
                sParaTemp.Add("total_fee", order.PayAmount.ToString("0.00"));//order.PayAmount.ToString("0.00")
                //sParaTemp.Add("total_fee", "0.01");//order.PayAmount.ToString("0.00")
                sParaTemp.Add("body", dto.OrderInfo);
                AlipaySubmit.BuildRequest(sParaTemp, "POST", "确认");
                return Content("");
            }
            catch (Exception e)
            {
                throw new ApplicationException(e.Message);
            }

        }
        public JsonResult Notify()
        {
            NLogLogger nlog = new NLogLogger();
            try
            {
            SortedDictionary<string, string> sPara = GetRequestPost();
            if (sPara.Count > 0)//判断是否有带返回参数
            {
                AlipayNotify aliNotify = new AlipayNotify();
                nlog.Info(JsonConvert.SerializeObject(sPara));
                bool verifyResult = aliNotify.Verify(sPara, Request.Form["notify_id"], Request.Form["sign"]);

                if (verifyResult)//验证成功
                {
                    string out_trade_no = Request.Form["out_trade_no"];

                    //支付宝交易号
                    string trade_no = Request.Form["trade_no"];

                    //交易状态
                    string trade_status = Request.Form["trade_status"];
                    if (Request.Form["trade_status"] == "TRADE_FINISHED")
                    { 
                        WSBService.RechargeFailure(out_trade_no);
                        return Json("fail");
                    }
                    else if (Request.Form["trade_status"] == "TRADE_SUCCESS")
                    {
                        WSBService.RechargeToWSBAccount(out_trade_no, trade_no);
                    }
                    return Json("success",JsonRequestBehavior.AllowGet);  //请不要修改或删除
                }
                else//验证失败
                {
                    return Json("fail", JsonRequestBehavior.AllowGet);
                }
            }
            else
            {
                return Json("无通知参数");
            }
               
            }
            catch (Exception e)
            {
              
                nlog.Info("支付宝通知数据：" + e.Message);
                return Json("fail");
            }
        }

        #region  app
        /// <summary>
        /// 用户充值-手机端
        /// </summary>
        /// <returns></returns>
        [HttpPost]
        public ActionResult ChargeSign(ChargeDto dto)
        {
            //dto.ReturnUrl = "";
            //Type type = dto.GetType();
            //PropertyInfo[] t = type.GetProperties();
            //Dictionary<string,string> dic=new Dictionary<string, string>();
            //foreach (var item in t)
            //{
            //   dic.Add(item.Name,item.GetValue(dto).ToString()); 
            //}
            //return Json(dic,JsonRequestBehavior.AllowGet);
            try
            {
                var order = WSBService.CreateWSBRechargeBill(dto);
                var noticeUrl = Url.AbsoluteAction("NotifyMobile", "AliPay");
                var amount = order.PayAmount;
                if (amount < 1)
                {
                    throw new ApplicationException("充值金额需大于1");
                }
                Dictionary<string, string> sParaTemp = new Dictionary<string, string>();
                sParaTemp.Add("service", Config.mobileService);
                sParaTemp.Add("partner", Config.partner);
                sParaTemp.Add("seller_id", Config.seller_id);
                sParaTemp.Add("_input_charset", Config.input_charset.ToLower());
                sParaTemp.Add("payment_type", Config.payment_type);
                sParaTemp.Add("notify_url", noticeUrl);
                sParaTemp.Add("return_url", dto.ReturnUrl);
                sParaTemp.Add("anti_phishing_key", Config.anti_phishing_key);
                //sParaTemp.Add("exter_invoke_ip", Config.exter_invoke_ip);
                sParaTemp.Add("out_trade_no", order.OrderId);
                sParaTemp.Add("subject", dto.OrderInfo);
                sParaTemp.Add("total_fee", order.PayAmount.ToString("0.00"));//order.PayAmount.ToString("0.00")
                //sParaTemp.Add("total_fee", "0.01");//order.PayAmount.ToString("0.00")
                sParaTemp.Add("body", "充值");

                var sign = AlipayCore.RsaSign(sParaTemp);
                var signLink = AlipaySignature.GetSignContent(sParaTemp);
                signLink += "&sign=\"" + HttpUtility.UrlEncode(sign) + "\"";
                signLink += "&sign_type=\"RSA\"";
                //AlipaySubmit.BuildRequest(sParaTemp, "POST", "确认");
                return Json(new { errorCode = 0, message = "创建签名成功", data = signLink }, JsonRequestBehavior.AllowGet);
            }
            catch (Exception e)
            {
                return Json(new { errorCode = -1, message = e.Message }, JsonRequestBehavior.AllowGet);
            }

        }
        public JsonResult NotifyMobile()
        {
            NLogLogger nlog = new NLogLogger();
            try
            {
                SortedDictionary<string, string> sPara = GetRequestPost();
                if (sPara.Count > 0)//判断是否有带返回参数
                {
                    AlipayNotify aliNotify = new AlipayNotify();
                    nlog.Info(JsonConvert.SerializeObject(sPara));
                    bool verifyResult = aliNotify.VerifyRsa(sPara, Request.Form["notify_id"], Request.Form["sign"]);

                    if (verifyResult)//验证成功
                    {
                        string out_trade_no = Request.Form["out_trade_no"];

                        //支付宝交易号
                        string trade_no = Request.Form["trade_no"];

                        //交易状态
                        string trade_status = Request.Form["trade_status"];
                        if (Request.Form["trade_status"] == "TRADE_FINISHED")
                        {
                            WSBService.RechargeFailure(out_trade_no);
                            return Json("fail");
                        }
                        else if (Request.Form["trade_status"] == "TRADE_SUCCESS")
                        {
                            WSBService.RechargeToWSBAccount(out_trade_no, trade_no);
                        }
                        return Json("success", JsonRequestBehavior.AllowGet);  //请不要修改或删除
                    }
                    else//验证失败
                    {
                        return Json("fail", JsonRequestBehavior.AllowGet);
                    }
                }
                else
                {
                    return Json("无通知参数");
                }

            }
            catch (Exception e)
            {

                nlog.Info("支付宝通知数据：" + e.Message);
                return Json("fail");
            }
        }


        #endregion
        /// <summary>
        /// 获取支付宝POST过来通知消息，并以“参数名=参数值”的形式组成数组
        /// </summary>
        /// <returns>request回来的信息组成的数组</returns>
        public SortedDictionary<string, string> GetRequestPost()
        {
            int i = 0;
            SortedDictionary<string, string> sArray = new SortedDictionary<string, string>();
            NameValueCollection coll;
            //Load Form variables into NameValueCollection variable.
            coll = Request.Form;

            // Get names of all forms into a string array.
            String[] requestItem = coll.AllKeys;

            for (i = 0; i < requestItem.Length; i++)
            {
                sArray.Add(requestItem[i], Request.Form[requestItem[i]]);
            }

            return sArray;
        }
    }
}